# -*- coding: utf-8 -*-
"""
decision_function精准率和召回率的平衡
Created on Wed Apr 25 09:01:22 2018

@author: Allen
"""
import numpy as np
from sklearn import datasets

digits = datasets.load_digits()
X = digits.data
y = digits.target.copy()

y[digits.target == 9] = 1
y[digits.target != 9] = 0

from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split( X, y, random_state = 666 )

from sklearn.linear_model import LogisticRegression
log_reg = LogisticRegression()
log_reg.fit( X_train, y_train )
print( log_reg.score( X_test, y_test ) ) # 0.975555555556

y_predict = log_reg.predict( X_test )

# 精准率
from sklearn.metrics import precision_score
print( precision_score( y_test, y_predict ) ) # 0.947368421053

# 召回率
from sklearn.metrics import recall_score
print( recall_score( y_test, y_predict ) ) # 0.8

# f1_score
from sklearn.metrics import f1_score
print( f1_score( y_test, y_predict ) ) # 0.867469879518

# 混淆矩阵
from sklearn.metrics import confusion_matrix

print( log_reg.decision_function( X_test ) )
print( log_reg.decision_function( X_test )[:10] )
'''
[-22.05698737 -33.02937619 -16.21332482 -80.37914497 -48.25127218
 -24.540052   -44.3917185  -25.04291075  -0.9782965  -19.71744559]
'''
print( log_reg.predict( X_test )[:10] ) # [0 0 0 0 0 0 0 0 0 0]

print( np.min( log_reg.decision_function( X_test ) ), np.max( log_reg.decision_function( X_test ) ) )
# -85.6860524125 19.8895700568

decision_scores = log_reg.decision_function( X_test )
y_log_predict1 = np.array( decision_scores >= 5, dtype = "int" )
print( "y_log_predict1的混淆矩阵是", confusion_matrix( y_test, y_log_predict1 ) )
print( "y_log_predict1的precision是", precision_score( y_test, y_log_predict1 ) ) # 0.96
print( "y_log_predict1的recall是", recall_score( y_test, y_log_predict1 ) ) # 0.533333333333
'''
对比第一个precision ，提高了一点，而recall下降了一些
'''

y_log_predict2 = np.array( decision_scores >= -5, dtype = "int" )
print( "y_log_predict2的混淆矩阵是", confusion_matrix( y_test, y_log_predict2 ) )
print( "y_log_predict2的precision是", precision_score( y_test, y_log_predict2 ) ) # 0.727272727273
print( "y_log_predict2的recall是", recall_score( y_test, y_log_predict2 ) ) # 0.888888888889
'''
当决策边界变为大于等于-5时，查准率明显降低，recall明显上升。
由此可以看出precision和recall这一组指标是相互制约，相互平衡的。
'''